package com.googlecode.monitoring.web;

import com.googlecode.monitoring.model.ItemToCheck;
import com.googlecode.monitoring.model.StateName;
import org.apache.log4j.Logger;
import org.springframework.core.io.Resource;

import java.io.*;
import java.util.Date;
import java.util.List;


public abstract class StatusBean {

	protected static Logger log = Logger.getLogger(StatusBean.class);

	protected boolean dataFound;
	protected Date lastModified;
	protected Boolean monitoringProcessUp;
	protected int outdatedItemsCount;
    private SettingsBean settings;
    private String statusURI;

	protected StatusBean() {
    }

    public StatusBean(SettingsBean settings) throws IOException {
        this.settings = settings;
	}

    protected void updateData(Resource statusResource) throws IOException{
        monitoringProcessUp = checkMonitoringProcessState(settings.getShellCommand(), settings.getProcessStateCommand());
        setStatusURI(statusResource.getURI().toString());
		try {
			lastModified = getResourceLastModifiedDate(statusResource);
			dataFound = true;
		} catch (FileNotFoundException e) {
			lastModified = null;
			dataFound = false;
		}
    }



    public String getStatusURI() {
        return statusURI;
    }

    public void setStatusURI(String statusURI) {
        this.statusURI = statusURI;
    }

    public boolean isDataFound() {
		return dataFound;
	}

	public Date getLastModified() {
		return lastModified;
	}

	public Boolean getMonitoringProcessUp() {
		return monitoringProcessUp;
	}

	public int getOutdatedItemsCount() {
		return outdatedItemsCount;
	}
	protected void setOutdatedItemsCount(int outdatedItemsCount) {
		this.outdatedItemsCount = outdatedItemsCount;
	}


	protected static Date getResourceLastModifiedDate(Resource stateResource) throws IOException {
		return new Date(stateResource.lastModified());
	}

	protected static boolean isLinuxOs() {
		return System.getProperty("os.name").matches("(?i).*linux.*");
	}

	protected static Boolean checkMonitoringProcessState(String shellCommand, String command) {
		//if (isLinuxOs()) {
			try {
				String result = execCommand(shellCommand, command).trim();
				return !result.isEmpty();
			}
			catch (IOException e) {
				return null;
			}
		//}
		//return null;
	}

	protected static String execCommand(String shellCommand, String command) throws IOException {
		log.debug("executing command: " + command);
		StringBuilder commandOutBuilder = new StringBuilder();

		boolean useShell = shellCommand != null && !shellCommand.isEmpty();

		Process p;
		if (useShell) {
			log.debug("using shell: " + shellCommand);
			p = Runtime.getRuntime().exec(shellCommand);
		} else {
			p = Runtime.getRuntime().exec(command);
		}

		OutputStreamWriter output = new OutputStreamWriter(p.getOutputStream());
		BufferedReader input = new BufferedReader(new InputStreamReader(p.getInputStream()));

		if (useShell) {
			output.write(command);
			output.write("\nexit\n");
			output.flush();
		}

		String line;
		while ((line = input.readLine()) != null) {
			commandOutBuilder.append(line);
		}
		input.close();
		String commandOut = commandOutBuilder.toString();
		log.debug("command out: " + commandOut);
		return commandOut;
	}

    public SettingsBean getSettings() {
        return settings;
    }

    public void setSettings(SettingsBean settings) {
        this.settings = settings;
    }

    protected static int calculateOutdatedItemsCount(List<? extends ItemToCheck> items) {
        int outdatedItemsCount = 0;
        for (ItemToCheck item : items) {
            if (item.getCurrentStateName().equals(StateName.EMAIL_SENT)) {
                outdatedItemsCount++;
            }
        }
        return outdatedItemsCount;
    }
}
